home *** CD-ROM | disk | FTP | other *** search
/ Language/OS - Multiplatform Resource Library / LANGUAGE OS.iso / p4 / p4-1_2a.lha / p4-1.2a / lib / p4_alloc.c < prev    next >
C/C++ Source or Header  |  1992-12-15  |  10KB  |  400 lines

  1. #include "p4.h"
  2. #include "p4_sys.h"
  3.  
  4. struct local_data *alloc_local_bm()
  5. {
  6.     struct local_data *l;
  7.  
  8.     l = (struct local_data *) p4_malloc(sizeof(struct local_data));
  9.     if (l == NULL)
  10.     {
  11.     p4_dprintf("OOPS: alloc_local_bm: p4_malloc failed \n");
  12.     return (l);
  13.     }
  14.  
  15.     l->am_bm = TRUE;
  16.     l->listener_fd = -1;
  17.     l->my_id = -1;
  18.     l->procgroup = NULL;
  19.     l->queued_messages = (struct p4_msg_queue *)
  20.     p4_malloc(sizeof(struct p4_msg_queue));
  21.     initialize_msg_queue(l->queued_messages);
  22.     l->soft_errors = 0;
  23.  
  24. #   ifdef CAN_DO_XDR
  25.     if ((l->xdr_buff = (char *) p4_malloc(XDR_BUFF_LEN)) == NULL)
  26.     {
  27.     p4_error("OOPS: alloc_local_bm: unable to malloc xdr_buff\n",NULL);
  28.     }
  29.     xdrmem_create(&(l->xdr_enc), l->xdr_buff, XDR_BUFF_LEN, XDR_ENCODE);
  30.     xdrmem_create(&(l->xdr_dec), l->xdr_buff, XDR_BUFF_LEN, XDR_DECODE);
  31. #   endif
  32.  
  33.     return (l);
  34. }
  35.  
  36. struct local_data *alloc_local_rm()
  37. {
  38.     struct local_data *l;
  39.  
  40.     l = (struct local_data *) p4_malloc(sizeof(struct local_data));
  41.     if (l == NULL)
  42.     {
  43.     p4_dprintf("OOPS: alloc_local_rm: p4_malloc failed \n");
  44.     return (l);
  45.     }
  46.  
  47.     l->am_bm = FALSE;
  48.     l->listener_fd = -1;
  49.     l->my_id = -1;
  50.     l->procgroup = NULL;
  51.     l->queued_messages = (struct p4_msg_queue *)
  52.     p4_malloc(sizeof(struct p4_msg_queue));
  53.     initialize_msg_queue(l->queued_messages);
  54.     l->soft_errors = 0;
  55.  
  56. #   ifdef CAN_DO_XDR
  57.     if ((l->xdr_buff = (char *) p4_malloc(XDR_BUFF_LEN)) == NULL)
  58.     {
  59.     p4_error("OOPS: alloc_local_rm: unable to malloc xdr_buff\n",NULL);
  60.     }
  61.     xdrmem_create(&(l->xdr_enc), l->xdr_buff, XDR_BUFF_LEN, XDR_ENCODE);
  62.     xdrmem_create(&(l->xdr_dec), l->xdr_buff, XDR_BUFF_LEN, XDR_DECODE);
  63. #   endif
  64.  
  65.     return (l);
  66. }                /* alloc_local_rm */
  67.  
  68. struct local_data *alloc_local_listener()
  69. {
  70.     struct local_data *l;
  71.  
  72.     l = (struct local_data *) p4_malloc(sizeof(struct local_data));
  73.  
  74.     l->am_bm = FALSE;
  75.     l->listener_fd = -1;
  76.     l->my_id = LISTENER_ID;
  77.     l->procgroup = NULL;
  78.     l->queued_messages = NULL;
  79.     l->xdr_buff = NULL;
  80.     l->soft_errors = 0;
  81.     return (l);
  82. }                /* alloc_local_listener */
  83.  
  84. struct local_data *alloc_local_slave()
  85. {
  86.     struct local_data *l;
  87.  
  88.     l = (struct local_data *) p4_malloc(sizeof(struct local_data));
  89.  
  90.     l->am_bm = FALSE;
  91.     l->listener_fd = -1;
  92.     l->my_id = -1;
  93.     l->procgroup = NULL;
  94.     l->queued_messages = (struct p4_msg_queue *)
  95.     p4_malloc(sizeof(struct p4_msg_queue));
  96.     initialize_msg_queue(l->queued_messages);
  97.     l->soft_errors = 0;
  98.  
  99. #   ifdef CAN_DO_XDR
  100.     if (!(p4_global->local_communication_only))
  101.     {
  102.         if ((l->xdr_buff = (char *) p4_malloc(XDR_BUFF_LEN)) == NULL)
  103.         {
  104.         p4_error("OOPS: alloc_local_slave: unable to malloc xdr_buff\n",NULL);
  105.         }
  106.         xdrmem_create(&(l->xdr_enc), l->xdr_buff, XDR_BUFF_LEN, XDR_ENCODE);
  107.         xdrmem_create(&(l->xdr_dec), l->xdr_buff, XDR_BUFF_LEN, XDR_DECODE);
  108.     }
  109. #   endif
  110.  
  111.     return (l);
  112. }
  113.  
  114. /*
  115.     This routine should be called before any sends and receives are done by
  116.     the user.  If not, some buffers may be lost.
  117. */
  118. P4VOID p4_set_avail_buff(bufidx,size)
  119. int bufidx;
  120. int size;
  121. {
  122.     p4_global->avail_buffs[bufidx].size = size;
  123.     p4_global->avail_buffs[bufidx].buff = NULL;
  124. }
  125.  
  126.  
  127. P4VOID init_avail_buffs()
  128. {
  129.     static int sizes[NUMAVAILS] = 
  130.             {64,256,1024,4096,16384,65536,262144,1048576};
  131.     int i;
  132.  
  133.     for (i = 0; i < NUMAVAILS; i++)
  134.     {
  135.         p4_global->avail_buffs[i].size = sizes[i];
  136.         p4_global->avail_buffs[i].buff = NULL;
  137.     }
  138. }
  139.  
  140. P4VOID p4_print_avail_buffs()
  141. {
  142.     int i, count;
  143.     struct p4_msg *next;
  144.  
  145.     p4_dprintf("avail lists for message buffers:\n");
  146.     p4_lock(&p4_global->avail_buffs_lock);
  147.     for (i = 0; i < NUMAVAILS; i++)
  148.     {
  149.     count = 0;
  150.     for (next = p4_global->avail_buffs[i].buff; next; next = next->link)
  151.          count++;
  152.     p4_dprintf("%d buffers of size %d\n",
  153.            count, p4_global->avail_buffs[i].size);
  154.     }
  155.     p4_unlock(&p4_global->avail_buffs_lock);
  156. }
  157.  
  158. struct p4_msg *alloc_p4_msg(msglen)
  159. int msglen;
  160. {
  161.     struct p4_msg *rmsg = NULL, **trailer;
  162.     int i, rounded;
  163.     P4BOOL found;
  164.  
  165.     p4_dprintfl(40, "allocating a buffer for message of size %d\n", msglen);
  166.  
  167. #   if defined(TCMP)
  168.  
  169.     rmsg = (struct p4_msg *) tcmp_allocate((sizeof(struct p4_msg) + msglen) - sizeof(char *));
  170.     p4_dprintfl(40, "allocated new buffer at 0x%x for msg of size %d\n",
  171.         rmsg, msglen);
  172.     rmsg->len = msglen;
  173.     return(rmsg);
  174.  
  175. #   else
  176.  
  177.     i = 0;
  178.     while ((i < NUMAVAILS) && (msglen > p4_global->avail_buffs[i].size))
  179.     i++;
  180.  
  181.     if (i == NUMAVAILS)        /* didn't find a big enough avail buffer */
  182.     {
  183.     rmsg = (struct p4_msg *)
  184.         p4_shmalloc((sizeof(struct p4_msg) + msglen) - sizeof(char *));
  185.     p4_dprintfl(40, "allocated new buffer at0x%x for message size %d\n",
  186.             rmsg, msglen);
  187.     }
  188.     else
  189.     {
  190.     rounded = p4_global->avail_buffs[i].size;
  191.     p4_lock(&p4_global->avail_buffs_lock);
  192.     if (p4_global->avail_buffs[i].buff)
  193.     {
  194.  
  195. #if defined(IPSC860)
  196.         rmsg = p4_global->avail_buffs[i].buff;
  197.         trailer = &(p4_global->avail_buffs[i].buff);
  198.         found = FALSE;
  199.         while (!found && (rmsg != NULL))
  200.         {
  201.         if (rmsg->msg_id == -1)
  202.         {
  203.             found = TRUE;
  204.         }
  205.         else if (msgdone((long) rmsg->msg_id))
  206.         {
  207.             rmsg->msg_id = -1;    
  208.             (p4_global->cube_msgs_out)--;
  209.             found = TRUE;
  210.         }
  211.         else
  212.         {
  213.             trailer = &((*trailer)->link);
  214.             rmsg = rmsg->link;
  215.         }
  216.         }
  217.         if (!found && (p4_global->cube_msgs_out > P4_MAX_CUBE_MSGS_OUT))
  218.         {
  219.         if ((rmsg = p4_global->avail_buffs[i].buff) != NULL)
  220.         {
  221.             msgwait((long) rmsg->msg_id);
  222.             rmsg->msg_id = -1;    
  223.             (p4_global->cube_msgs_out)--;
  224.             found = TRUE;
  225.         }
  226.         }
  227.         if (!found)
  228.         {
  229.         rmsg = (struct p4_msg *)
  230.             p4_shmalloc((sizeof(struct p4_msg) + rounded) - sizeof(char *));
  231.         p4_dprintfl(40, "allocated new buffer at 0x%x of size %d for message size %d\n", rmsg, rounded, msglen);
  232.         }
  233.         else
  234.         {
  235.         *trailer = rmsg->link;
  236.         p4_dprintfl(40, "reused a buffer of size %d for message size %d\n",
  237.                 rounded, msglen);
  238.         }
  239. #else
  240.         rmsg = p4_global->avail_buffs[i].buff;
  241.         p4_global->avail_buffs[i].buff = rmsg->link;
  242.         p4_dprintfl(40, "reused a buffer of size %d for message size %d\n",
  243.             rounded, msglen);
  244. #endif
  245.  
  246.         p4_unlock(&p4_global->avail_buffs_lock);
  247.     }
  248.     else
  249.     {
  250.         p4_unlock(&p4_global->avail_buffs_lock);
  251.         rmsg = (struct p4_msg *)
  252.         p4_shmalloc((sizeof(struct p4_msg) + rounded) - sizeof(char *));
  253.         p4_dprintfl(40, "allocated new buffer at 0x%x of size %d for message size %d\n", rmsg, rounded, msglen);
  254.     }
  255.     }
  256.  
  257.     if ((rmsg == NULL) && !SOFTERR)
  258.     p4_error("alloc_p4_msg failed", 0);
  259.  
  260.     rmsg->len = msglen;
  261.     return(rmsg);
  262.  
  263. #   endif
  264. }                /* alloc_p4_msg */
  265.  
  266. P4VOID free_p4_msg(tmsg)
  267. struct p4_msg *tmsg;
  268. {
  269.     int i, msglen;
  270.     struct p4_msg *p;
  271.  
  272.     msglen = tmsg->len;
  273.     p4_dprintfl(40, "freeing a buffer with message size %d\n", msglen);
  274.  
  275.     /* Sanity check here as bad message pointer causes havoc */
  276.  
  277.     if ((msglen < 0) || (msglen > P4_MAX_MSGLEN))
  278.     p4_error("free_p4_msg: bad hdr: msglen out of range", msglen);
  279.  
  280. #   if defined(TCMP)
  281.     if (tmsg)
  282.     tcmp_deallocate(tmsg);
  283.     return;
  284.  
  285. #   else
  286.  
  287.     i = 0;
  288.     while ((i < NUMAVAILS) && (msglen > p4_global->avail_buffs[i].size))
  289.     i++;
  290.  
  291.     if (i == NUMAVAILS)
  292.     {
  293.     /* buffer being freed is not a kept size */
  294.     p4_shfree(tmsg);
  295.     p4_dprintfl(40, "deallocated a buffer at %d for message size %d\n",
  296.             tmsg, msglen);
  297.     }
  298.     else
  299.     {
  300.     /* hook new buffer in at end of list */
  301.     p4_lock(&p4_global->avail_buffs_lock);
  302.     if ((p = p4_global->avail_buffs[i].buff) == NULL)
  303.         p4_global->avail_buffs[i].buff = tmsg;
  304.     else
  305.     {
  306.         while (p->link != NULL)
  307.         p = p->link;
  308.         p->link = tmsg;
  309.     }
  310.     tmsg->link = NULL;
  311.     p4_unlock(&p4_global->avail_buffs_lock);
  312.     p4_dprintfl(40, "saved a buffer of size %d in avail list for size %d\n",
  313.             msglen, p4_global->avail_buffs[i].size);
  314.     }
  315.  
  316. #   endif
  317. }                /* free_p4_msg */
  318.  
  319. P4VOID alloc_global()
  320. {
  321.     int i;
  322.     struct p4_global_data *g;
  323.  
  324.     p4_global = (struct p4_global_data *) p4_shmalloc(sizeof(struct p4_global_data));
  325.     if (p4_global == NULL)
  326.     {
  327.     p4_error("alloc_global: alloc_global failed\n", sizeof(struct p4_global_data));
  328.     }
  329.     g = p4_global;
  330.  
  331. #ifdef SYSV_IPC
  332.     g->slave_lock.semid = sysv_semid0;
  333.     g->slave_lock.semnum = 1;
  334.     g->sysv_semid[0] = sysv_semid0;
  335.     g->sysv_num_semids = 1;
  336.     g->sysv_next_lock = 2;  /* shmem_lock is 0 & slave_lock is 1 */
  337. #else
  338.     p4_lock_init(&g->slave_lock);
  339. #endif
  340.  
  341.     g->listener_pid = -1;
  342.     g->listener_port = -1;
  343.  
  344.     g->cube_msgs_out = 0;
  345.  
  346.     g->local_slave_count = 0;
  347.     g->local_communication_only = TRUE;
  348.     g->n_forked_pids = 0;
  349.  
  350.     for (i = 0; i < P4_MAX_MSG_QUEUES; i++)
  351.     {
  352.     initialize_msg_queue(&g->shmem_msg_queues[i]);
  353.     g->dest_id[i] = -1;
  354.     }
  355.  
  356.     p4_lock_init(&g->avail_buffs_lock);
  357.     init_avail_buffs();
  358.     p4_lock_init(&g->avail_quel_lock);
  359.     g->avail_quel = NULL;
  360.  
  361.     g->num_in_proctable = 0;
  362.     g->num_installed = 0;
  363.     g->my_host_name[0] = '\0';
  364.     get_qualified_hostname(g->my_host_name);
  365.  
  366.     p4_barrier_init(&(g->cluster_barrier));
  367.  
  368.     sprintf(g->application_id, "p4_%-8d", getpid());
  369.  
  370. #   if defined(P4BSD)
  371.     g->max_connections = getdtablesize();
  372. #   endif
  373.  
  374. #   if defined(P4SYSV)
  375. #       if defined(CRAY) || defined(RS6000) || \
  376.        defined(IBM3090) || defined(SYMMETRY_PTX)
  377.               g->max_connections = getdtablesize();
  378. #       else
  379. #       if defined(IPSC860) || defined(HP)  /* HP probably supports more */
  380.               g->max_connections = 20;
  381. #       else
  382.               g->max_connections = (int) ulimit(4,0);
  383. #       endif
  384. #       endif
  385. #   endif
  386.  
  387. }
  388.  
  389. struct listener_data *alloc_listener_info()
  390. {
  391.     struct listener_data *l;
  392.  
  393.     l = (struct listener_data *) p4_malloc(sizeof(struct listener_data));
  394.  
  395.     l->listening_fd = -1;
  396.     l->slave_fd = -1;
  397.  
  398.     return (l);
  399. }
  400.